package ricky.quadtree
{
	import flash.geom.Rectangle;

	/**
	 * 线性四叉树区域节点
	 */
	public class BoundsNode extends Node
	{
		function BoundsNode(bounds:Rectangle, depth:int, maxChildren:int=NaN, maxDepth:int=NaN)
		{
			_classConstructor = BoundsNode;
			super(bounds, depth, maxChildren, maxDepth);
			this._stuckChildren = [];
 		}
		
		protected var _stuckChildren:Array = null;
		
		//we use this to collect and conctenate items being retrieved. This way
		//we dont have to continuously create new Array instances.
		//Note, when returned from QuadTree.retrieve, we then copy the array
		protected var _out:Array = [];
		
		public override function insert(item)
		{	
			if(this.nodes.length)
			{
				var index = this._findIndex(item);
				var node = this.nodes[index];
				
				//todo: make _bounds bounds
				if(item.x >= node._bounds.x &&
					item.x + item.width <= node._bounds.x + node._bounds.width &&
					item.y >= node._bounds.y &&
					item.y + item.height <= node._bounds.y + node._bounds.height)
				{
					this.nodes[index].insert(item);
				}
				else
				{			
					this._stuckChildren.push(item);
				}
				
				return;
			}
			
			this.children.push(item);
			
			var len = this.children.length;
			
			if(!(this._depth >= this._maxDepth) && 
				len > this._maxChildren)
			{
				this.subdivide();
				
				for(var i = 0; i < len; i++)
				{
					this.insert(this.children[i]);
				}
				
				this.children.length = 0;
			}
		}
		
		public function getChildren()
		{
			return this.children.concat(this._stuckChildren);
		}
		
		public override function retrieve(item)
		{
			var out:Array = this._out;
			out.length = 0;
			if(this.nodes.length)
			{
				var index = this._findIndex(item);
				out.concat(this.nodes[index].retrieve(item));
//				out.push.apply(out, this.nodes[index].retrieve(item));
			}
			out=out.concat(this._stuckChildren);
			out=out.concat(this.children);
//			out.push.apply(out, this._stuckChildren);
//			out.push.apply(out, this.children);
			
			return out;
		}
		
		public override function clear()
		{
			
			this._stuckChildren.length = 0;
			
			//array
			this.children.length = 0;
			
			var len = this.nodes.length;
			
			if(!len)
			{
				return;
			}
			
			for(var i = 0; i < len; i++)
			{
				this.nodes[i].clear();
			}
			
			//array
			this.nodes.length = 0;	
			
			//we could call the super clear function but for now, im just going to inline it
			//call the hidden super.clear, and make sure its called with this = this instance
			//Object.getPrototypeOf(BoundsNode.prototype).clear.call(this);
		}
		
		protected var getChildCount;
	}
}